﻿using System;
using System.Collections.Generic;
using System.Formats.Asn1;
using System.Linq;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using XingLucifer.Devices.Models;
using XingLucifer.IBase;
using XingLucifer.IBase.Enums;

namespace XingLucifer.Devices.Devices.Testers
{
    public class ST5520 : IDevices
    {
        private ICommunication _com;
        private CancellationTokenSource _tokenSource;
        public ST5520(ICommunication com, CancellationTokenSource tokenSource)
        {
            _com = com;
            _tokenSource = tokenSource;
        }

        public bool WriteClass<TClass>(TClass value, int address, int count = 3) where TClass : class
        {
            throw new NotImplementedException("未实现");
        }

        /// <summary>
        /// 查询测量值与判定结果
        /// </summary>
        /// <typeparam name="TClass">ST5520ResultModel</typeparam>
        /// <param name="address">未用</param>
        /// <param name="obj">ST5520ResultModel对象</param>
        /// <param name="count">重试次数</param>
        /// <returns></returns>
        public TClass ReadClass<TClass>(int address, TClass obj = null, int count = 3) where TClass : class
        {
            for (int i = 0; i < count; i++)
            {
                try
                {
                    ST5520ResultModel model = new ST5520ResultModel();
                    _com.Write(Encoding.ASCII.GetBytes(":MEASure:RESult?\r\n"));
                    byte[] bytes = _com.Read(20);
                    string[] str = Encoding.ASCII.GetString(bytes).Trim().Split(',');
                    model.Test_Value = Convert.ToSingle(str[0]) / 1000000.0F;
                    model.Test_Result = str[1];
                    return model as TClass;
                }
                catch (Exception)
                {
                    _com.ReconnectDisconnection?.Invoke(_com, _com.Index, _com.IP, _com.Port, _com.DeviceType, _com.TaskType, _com.ServiceName, _tokenSource);
                }
            }
            return default;
        }

        public Task Read()
        {
            throw new NotImplementedException("未实现");
        }

        public bool WriteSingle(object value, int address, int offset, int length, int count = 3)
        {
            byte[] bytes = Encoding.ASCII.GetBytes($"{value}\r\n");
            for (int i = 0; i < count; i++)
            {
                try
                {
                    _com.Write(bytes);
                    return true;
                }
                catch (Exception)
                {
                    _com.ReconnectDisconnection?.Invoke(_com, _com.Index, _com.IP, _com.Port, _com.DeviceType, _com.TaskType, _com.ServiceName, _tokenSource);
                }
            }
            return false;
        }

        /// <summary>
        /// 读取仪器的状态
        /// 0 ：停止中
        /// 1 ：测试中
        /// 2 ：放电中
        /// </summary>
        /// <typeparam name="TValue">string</typeparam>
        /// <param name="address">0=>读取仪器状态 1=>获取指令执行状态</param>
        /// <param name="length">读取长度</param>
        /// <param name="count">重试次数</param>
        /// <returns></returns>
        public TValue? ReadSingle<TValue>(int address, int length, int count = 3)
        {
            for (int i = 0; i < count; i++)
            {
                try
                {
                    string cmd = string.Empty;
                    switch (address)
                    {
                        case 0:
                            cmd = "STATe";
                            length = 3;
                            break;
                        case 1:
                            cmd = "ESR";//测试了没有作用
                            length = 3;
                            break;
                    }
                    byte[] bytes = Encoding.ASCII.GetBytes($":{cmd}?\r\n");
                    _com.Write(bytes);
                    var datas = _com.Read(length);
                    return (TValue?)(object)Encoding.ASCII.GetString(datas).Trim();
                }
                catch (Exception)
                {
                    _com.ReconnectDisconnection?.Invoke(_com, _com.Index, _com.IP, _com.Port, _com.DeviceType, _com.TaskType, _com.ServiceName, _tokenSource);
                }
            }
            return default;
        }

        public bool Open() => _com.Open();

        public string Close() => _com.Close();
    }
}
